package com.ccteam.admin.viewmodels.music

import android.app.Application
import androidx.lifecycle.*
import com.ccteam.admin.ARTIST_SEPARATOR
import com.ccteam.admin.repositories.MusicAdminRepository
import com.ccteam.admin.utils.ErrorMessage
import com.ccteam.admin.utils.Event
import com.ccteam.admin.utils.LoadMessage
import com.ccteam.admin.view.bean.SelectInfoResult
import com.ccteam.admin.vo.Resource
import com.ccteam.network.ApiError
import dagger.hilt.android.lifecycle.HiltViewModel
import kotlinx.coroutines.launch
import javax.inject.Inject

/**
 * @author Xiaoc
 * @since 2021/3/3
 *
 * 编辑歌手ViewModel层
 */
@HiltViewModel
class MusicEditViewModel @Inject constructor(
    application: Application,
    private val musicRepository: MusicAdminRepository,
    savedStateHandle: SavedStateHandle
): AndroidViewModel(application) {


    private val _enableEditButton = MediatorLiveData<Boolean>()
    val enableEditButton: LiveData<Boolean> get() = _enableEditButton

    private val _enableDeleteButton = MediatorLiveData<Boolean>()
    val enableDeleteButton: LiveData<Boolean> get() = _enableDeleteButton

    private val musicNameSuccess = MutableLiveData(false)
    private val durationSuccess = MutableLiveData(false)
    private val songYearSuccess = MutableLiveData(false)
    private val trackSuccess = MutableLiveData(false)
    private val artistsSuccess = MutableLiveData(false)

    private val musicIdLiveData = MutableLiveData<String>()

    private val _selectArtistList = MutableLiveData<MutableList<SelectInfoResult>>(mutableListOf())
    val selectArtistList: LiveData<MutableList<SelectInfoResult>> get() = _selectArtistList

    var originMusicInfo: MusicEditInfo? = null
    private set

    private val _editMusicInfo = MutableLiveData<MusicEditInfo>()
    val editMusicInfo: LiveData<MusicEditInfo> get() = _editMusicInfo

    private val _loadingMessage = MutableLiveData<LoadMessage>(LoadMessage.NotLoading)
    val loadMessage: LiveData<LoadMessage> get() = _loadingMessage

    /**
     * 编辑时的加载信息
     */
    private val _editLoadMessage = MediatorLiveData<Event<LoadMessage>>()
    val editLoadMessage: LiveData<Event<LoadMessage>> get() = _editLoadMessage

    /**
     * 删除时的加载信息
     */
    private val _deleteLoadMessage = MediatorLiveData<Event<LoadMessage>>()
    val deleteLoadMessage: LiveData<Event<LoadMessage>> get() = _deleteLoadMessage

    private val _musicUrl = MutableLiveData<Pair<String,String>>()
    val musicUrl: LiveData<Pair<String,String>> get() = _musicUrl

    init {
        _enableEditButton.addSource(musicNameSuccess){
            _enableEditButton.value = it && durationSuccess.value == true &&
                    songYearSuccess.value == true && trackSuccess.value == true &&
                    artistsSuccess.value == true &&
                    _editLoadMessage.value?.peekContent() !is LoadMessage.Loading &&
                    _deleteLoadMessage.value?.peekContent() !is LoadMessage.Loading
        }
        _enableEditButton.addSource(durationSuccess){
            _enableEditButton.value = it && musicNameSuccess.value == true &&
                    songYearSuccess.value == true && trackSuccess.value == true &&
                    artistsSuccess.value == true &&
                    _editLoadMessage.value?.peekContent() !is LoadMessage.Loading &&
                    _deleteLoadMessage.value?.peekContent() !is LoadMessage.Loading
        }
        _enableEditButton.addSource(songYearSuccess){
            _enableEditButton.value = it && musicNameSuccess.value == true &&
                    durationSuccess.value == true && trackSuccess.value == true &&
                    artistsSuccess.value == true &&
                    _editLoadMessage.value?.peekContent() !is LoadMessage.Loading &&
                    _deleteLoadMessage.value?.peekContent() !is LoadMessage.Loading
        }
        _enableEditButton.addSource(trackSuccess){
            _enableEditButton.value = it && durationSuccess.value == true &&
                    songYearSuccess.value == true && musicNameSuccess.value == true &&
                    artistsSuccess.value == true &&
                    _editLoadMessage.value?.peekContent() !is LoadMessage.Loading &&
                    _deleteLoadMessage.value?.peekContent() !is LoadMessage.Loading
        }
        _enableEditButton.addSource(artistsSuccess){
            _enableEditButton.value = it && durationSuccess.value == true &&
                    songYearSuccess.value == true && trackSuccess.value == true &&
                    musicNameSuccess.value == true &&
                    _editLoadMessage.value?.peekContent() !is LoadMessage.Loading &&
                    _deleteLoadMessage.value?.peekContent() !is LoadMessage.Loading
        }
        _enableEditButton.addSource(_editLoadMessage){
            _enableEditButton.value = it.peekContent() !is LoadMessage.Loading && durationSuccess.value == true &&
                    songYearSuccess.value == true && trackSuccess.value == true &&
                    musicNameSuccess.value == true &&
                    _deleteLoadMessage.value?.peekContent() !is LoadMessage.Loading
            _enableDeleteButton.value = it.peekContent() !is LoadMessage.Loading &&
                    _deleteLoadMessage.value?.peekContent() !is LoadMessage.Loading
        }

        _enableEditButton.addSource(_deleteLoadMessage){
            _enableEditButton.value = it.peekContent() !is LoadMessage.Loading && durationSuccess.value == true &&
                    songYearSuccess.value == true && trackSuccess.value == true &&
                    musicNameSuccess.value == true &&
                    _editLoadMessage.value?.peekContent() !is LoadMessage.Loading
            _enableDeleteButton.value = it.peekContent() !is LoadMessage.Loading &&
                    _editLoadMessage.value?.peekContent() !is LoadMessage.Loading
        }

        _enableEditButton.addSource(musicIdLiveData){
            refreshMusicInfo()
        }

        val musicId = savedStateHandle.get<String>("musicId")
        musicId?.let {
            musicIdLiveData.value = it
        }
    }

    fun refreshMusicInfo(){
        _loadingMessage.value = LoadMessage.Loading

        musicIdLiveData.value?.let { musicId ->
            viewModelScope.launch {
                val result = musicRepository.getMusicInfo(musicId)

                if(result is Resource.Success){

                    originMusicInfo = MusicEditInfo.toMusicEditInfo(result.data)

                    val selectArtists = result.data?.artists?.split(ARTIST_SEPARATOR)?.mapIndexed { index, v ->
                        SelectInfoResult(result.data.artistsId[index],v)
                    }?.toMutableList() ?: mutableListOf()
                    _selectArtistList.value = selectArtists

                    _editMusicInfo.value = MusicEditInfo.toMusicEditInfo(result.data)

                    setArtistsSuccess(selectArtists.isNotEmpty())

                    _musicUrl.value = Pair(result.data?.url ?: "",result.data?.maxBitrate ?: "")

                    _loadingMessage.value = LoadMessage.NotLoading
                } else {
                    _loadingMessage.value = LoadMessage.Error(ErrorMessage(ApiError.unknownCode,result.message))
                }
            }
        }
    }

    /**
     * 更新编辑后的音乐信息，因为在外部设置不同的更新属性时会导致一些问题
     * 所以手动提供此方法进行调用
     */
    fun updateMusicEditInfo(){
        _editMusicInfo.value = _editMusicInfo.value
    }

    /**
     * 添加已选择的歌手内容
     */
    fun addSelectArtist(artistInfo: SelectInfoResult){
        // 如果已选择中已包含了选择的内容，则不做其他处理
        if(_selectArtistList.value?.contains(artistInfo) == true){
            return
        }
        _selectArtistList.value?.add(artistInfo)
        _selectArtistList.value = _selectArtistList.value

        setArtistsSuccess(true)
    }

    /**
     * 取消已选择的歌手
     */
    fun removeSelectArtist(artistInfo: SelectInfoResult){
        _selectArtistList.value?.remove(artistInfo)

        val newList = _selectArtistList.value?.map {
            it.copy()
        }?.toMutableList() ?: mutableListOf()
        _selectArtistList.value = newList

        setArtistsSuccess(!newList.isNullOrEmpty())
    }

    /**
     * 删除歌曲信息
     */
    fun deleteMusicInfo(){
        _deleteLoadMessage.value = Event(LoadMessage.Loading)

        viewModelScope.launch {
            originMusicInfo?.id?.let {
                val result = musicRepository.deleteMusicInfo(it)

                if(result is Resource.Success){
                    _deleteLoadMessage.value = Event(LoadMessage.Success)
                } else {
                    _deleteLoadMessage.value = Event(LoadMessage.Error(ErrorMessage(ApiError.serverErrorCode,result.message)))
                }
            }
        }
    }



    fun setMusicName(name: String){
        _editMusicInfo.value?.name = name
    }
    fun setMusicNameSuccess(success: Boolean){
        musicNameSuccess.value = success
    }

    fun setDuration(duration: String){
        _editMusicInfo.value?.duration = duration
    }
    fun setDurationSuccess(success: Boolean){
        durationSuccess.value = success
    }

    fun setSongYear(songYear: String){
        _editMusicInfo.value?.songYear = songYear
    }
    fun setSongYearSuccess(success: Boolean){
        songYearSuccess.value = success
    }

    fun setTrack(track: String){
        _editMusicInfo.value?.track = track
    }
    fun setTrackSuccess(success: Boolean){
        trackSuccess.value = success
    }

    fun setLrc(lrc: String){
        _editMusicInfo.value?.lrc = lrc
    }

    fun setArtistsSuccess(success: Boolean){
        artistsSuccess.value = success
    }

    fun publishMusicInfo(){
        if(_editMusicInfo.value == null){
            _editLoadMessage.value = Event(LoadMessage.Error(ErrorMessage(ApiError.unknownCode,"编辑数据为空")))
            return
        }
        if(_selectArtistList.value.isNullOrEmpty()){
            _editLoadMessage.value = Event(LoadMessage.Error(ErrorMessage(ApiError.unknownCode,"歌手列表为空，请选择")))
            return
        }
        _editLoadMessage.value = Event(LoadMessage.Loading)

        viewModelScope.launch {

            val artistsId = _selectArtistList.value!!.map {
                it.selectId
            }

            val artistNameBuilder = StringBuilder()

            _selectArtistList.value!!.forEach {
                artistNameBuilder.append("${it.selectTitle}/")
            }
            // 去掉歌手字符串中最后的 "/"
            artistNameBuilder.deleteAt(artistNameBuilder.length - 1)

            val result = musicRepository.editMusicInfo(
                _editMusicInfo.value!!.toEditMusicInfoDto(artistIds = artistsId,artistsName = artistNameBuilder.toString())
            )
            if(result is Resource.Success){
                _editLoadMessage.value = Event(LoadMessage.Success)
            } else {
                _editLoadMessage.value = Event(LoadMessage.Error(ErrorMessage(ApiError.serverErrorCode,result.message)))
            }
        }
    }

}